#!/usr/bin/env python3
"""
Speech Convert - 统一入口点

整合语音识别 WebSocket 服务和文本处理 HTTP API
"""

import argparse
import asyncio
import json
import logging
import os
import sys
import time
from contextlib import asynccontextmanager
from typing import Any, Dict, Optional

import uvicorn
from fastapi import FastAPI, Request, WebSocket, WebSocketDisconnect
from fastapi.middleware.cors import CORSMiddleware
from fastapi.responses import HTMLResponse, JSONResponse

from speech_convert.utils.console_style import (print_error, print_info,
                                                print_loading, print_stage,
                                                print_success)

from .config.funasr_config import CONFIG
from .config.logging_config import (get_app_logger, log_api_request,
                                    log_performance, setup_logging)
from .server.funasr_wss_server import clear_websocket, ws_serve
from .text_processing.api import router as text_processing_router

# 初始化日志系统
setup_logging(level="INFO")
logger = get_app_logger("main")

# 全局变量
websocket_users = set()
model_manager = None
response_manager = None
speaker_manager = None
args = None  # 添加全局args变量


def create_parser() -> argparse.ArgumentParser:
    """创建命令行参数解析器"""
    parser = argparse.ArgumentParser(
        description="Speech Convert - 语音识别与文本处理服务",
        formatter_class=argparse.RawDescriptionHelpFormatter,
        epilog="""
使用示例：
  # 默认启动
  python -m speech_convert.main

  # 自定义端口和主机
  python -m speech_convert.main --port 8080 --host 0.0.0.0

  # 开发模式（自动重载）
  python -m speech_convert.main --reload

  # 调试模式
  python -m speech_convert.main --log-level debug

  # 自定义模型配置
  python -m speech_convert.main --vad_model custom_model --asr_model custom_asr

  # GPU 模式
  python -m speech_convert.main --ngpu 1 --device cuda
        """
    )

    # HTTP 服务器参数
    parser.add_argument(
        "--host",
        default=CONFIG.server.DEFAULT_HOST,
        help=f"服务器主机地址 (默认: {CONFIG.server.DEFAULT_HOST})"
    )
    parser.add_argument(
        "--port",
        type=int,
        default=CONFIG.server.DEFAULT_PORT,
        help=f"FastAPI 服务端口 (默认: {CONFIG.server.DEFAULT_PORT})"
    )
    parser.add_argument(
        "--reload",
        action="store_true",
        help="开发模式，自动重载代码变更"
    )
    parser.add_argument(
        "--log-level",
        type=str,
        default="info",
        required=False,
        help="日志级别"
    )

    # FunASR 模型参数
    parser.add_argument(
        "--vad_model",
        type=str,
        default=CONFIG.model.VAD_MODEL,
        help="VAD 语音活动检测模型 (默认: %(default)s)"
    )
    parser.add_argument(
        "--vad_model_revision",
        type=str,
        default=CONFIG.model.VAD_MODEL_REVISION,
        help="VAD 模型版本 (默认: %(default)s)"
    )
    parser.add_argument(
        "--asr_model_online",
        type=str,
        default=CONFIG.model.ASR_MODEL_ONLINE,
        help="ASR 在线流式模型 (默认: %(default)s)"
    )
    parser.add_argument(
        "--asr_model_online_revision",
        type=str,
        default=CONFIG.model.ASR_MODEL_ONLINE_REVISION,
        help="ASR 在线模型版本 (默认: %(default)s)"
    )
    parser.add_argument(
        "--asr_model",
        type=str,
        default=CONFIG.model.ASR_MODEL,
        help="ASR 离线模型 (默认: %(default)s)"
    )
    parser.add_argument(
        "--asr_model_revision",
        type=str,
        default=CONFIG.model.ASR_MODEL_REVISION,
        help="ASR 离线模型版本 (默认: %(default)s)"
    )
    parser.add_argument(
        "--punc_model",
        type=str,
        default=CONFIG.model.PUNC_MODEL,
        help="标点符号模型 (默认: %(default)s)"
    )
    parser.add_argument(
        "--punc_model_revision",
        type=str,
        default=CONFIG.model.PUNC_MODEL_REVISION,
        help="标点符号模型版本 (默认: %(default)s)"
    )

    # 硬件配置参数
    parser.add_argument(
        "--ngpu",
        type=int,
        default=CONFIG.server.DEFAULT_NGPU,
        help="GPU 数量，0表示仅使用CPU (默认: %(default)s)"
    )
    parser.add_argument(
        "--device",
        type=str,
        default=CONFIG.server.DEFAULT_DEVICE,
        choices=["cpu", "cuda", "mps"],
        help="计算设备 (默认: %(default)s)"
    )
    parser.add_argument(
        "--ncpu",
        type=int,
        default=CONFIG.server.DEFAULT_NCPU,
        help="CPU 核心数 (默认: %(default)s)"
    )

    return parser


@asynccontextmanager
async def lifespan(app: FastAPI):
    """应用生命周期管理"""
    # 启动时初始化
    start_time = time.time()
    logger.info("🚀 正在初始化语音识别服务...")

    global model_manager, response_manager, speaker_manager, websocket_users, args

    # 使用 server_initialization 进行初始化
    try:
        logger.info("📋 使用命令行参数初始化...")

        # 创建初始化器并使用命令行参数
        from .server.server_initialization import ServerInitializer
        initializer = ServerInitializer()
        initializer.args = args  # 使用已解析的命令行参数

        # 初始化管理器和模型
        speaker_manager, response_manager = initializer.initialize_managers()
        model_manager = initializer.load_models()

        websocket_users = set()

        duration = time.time() - start_time
        log_performance("app_startup", duration)
        logger.info(f"✅ 语音识别服务初始化完成，总耗时: {duration:.2f}秒")

        # 打印访问地址信息
        logger.info("🌐 服务访问地址:")
        # 如果监听的是 0.0.0.0，显示本地访问地址
        local_host = "127.0.0.1" if server_host == "0.0.0.0" else server_host

                # 使用 ANSI 颜色代码让链接更醒目
        blue = "\033[94m"
        green = "\033[92m"
        magenta = "\033[95m"  # 改为洋红色，更柔和
        cyan = "\033[96m"
        reset = "\033[0m"

        logger.info(f"  🏠 根路径: {blue}http://{local_host}:{server_port}/{reset}")
        logger.info(f"  🔌 WebSocket: {green}ws://{local_host}:{server_port}/ws{reset}")
        logger.info(f"  📚 API 文档: {magenta}http://{local_host}:{server_port}/docs{reset}")
        logger.info(f"  💚 健康检查: {cyan}http://{local_host}:{server_port}/health{reset}")

        # 打印模型配置信息
        logger.info("📊 模型配置:")
        purple = "\033[95m"
        orange = "\033[33m"
        logger.info(f"  🎤 VAD模型: {purple}{args.vad_model}{reset}")
        logger.info(f"  🔄 ASR在线模型: {purple}{args.asr_model_online}{reset}")
        logger.info(f"  📝 ASR离线模型: {purple}{args.asr_model}{reset}")
        logger.info(f"  🎯 标点模型: {purple}{args.punc_model}{reset}")
        logger.info(f"  🖥️ 设备: {orange}{args.device} (GPU: {args.ngpu}, CPU: {args.ncpu}){reset}")

    except Exception as e:
        logger.error(f"❌ 语音识别服务初始化失败: {e}")
        raise

    yield

    # 关闭时清理
    logger.info("🔄 正在清理资源...")
    cleanup_start = time.time()
    try:
        await clear_websocket()
        duration = time.time() - cleanup_start
        log_performance("app_shutdown", duration)
        logger.info(f"✅ 资源清理完成，耗时: {duration:.2f}秒")
    except Exception as e:
        logger.error(f"⚠️ 资源清理时出错: {e}")


def create_fastapi_app() -> FastAPI:
    """创建 FastAPI 应用"""
    app = FastAPI(
        title="Speech Convert API",
        description="语音识别和文本处理综合 API 服务",
        version="1.0.0",
        lifespan=lifespan
    )

    # 添加 CORS 中间件
    app.add_middleware(
        CORSMiddleware,
        allow_origins=["*"],
        allow_credentials=True,
        allow_methods=["*"],
        allow_headers=["*"],
    )

    # 添加请求日志中间件
    @app.middleware("http")
    async def log_requests(request: Request, call_next):
        """记录 HTTP 请求日志"""
        start_time = time.time()

        # 处理请求
        response = await call_next(request)

        # 计算处理时间
        duration = time.time() - start_time

        # 记录请求日志
        log_api_request(
            method=request.method,
            path=str(request.url.path),
            status_code=response.status_code,
            duration=duration,
            client_ip=request.client.host if request.client else "unknown"
        )

        return response

    # 挂载文本处理路由
    app.include_router(text_processing_router, prefix="/api/v1")

    @app.get("/")
    async def root():
        """根路径"""
        return {
            "message": "Speech Convert API 服务",
            "version": "1.0.0",
            "services": {
                "websocket": "语音识别 WebSocket 服务",
                "http_api": "文本处理 HTTP API"
            },
            "endpoints": {
                "websocket": "/ws",
                "text_processing": "/api/v1/text",
                "docs": "/docs"
            }
        }

    @app.get("/health")
    async def health_check():
        """健康检查"""
        return {
            "status": "healthy",
            "services": {
                "websocket": "running",
                "text_processing": "running"
            },
            "models": {
                "asr": model_manager.asr is not None if model_manager else False,
                "asr_streaming": model_manager.asr_streaming is not None if model_manager else False,
                "vad": model_manager.vad is not None if model_manager else False,
                "punc": model_manager.punc is not None if model_manager else False
            }
        }



    @app.exception_handler(Exception)
    async def global_exception_handler(request, exc):
        """全局异常处理"""
        logger.error(f"未处理的异常: {exc}")
        return JSONResponse(
            status_code=500,
            content={
                "error": "内部服务器错误",
                "message": str(exc),
                "type": type(exc).__name__
            }
        )

    return app


def start_server(args: argparse.Namespace) -> None:
    """启动服务器"""

    print_stage("环境准备")
    print_success("环境变量已设置")
    print_info(f"🎯 启动命令: uv run python -m speech_convert.main --host {args.host} --port {args.port} --log-level {args.log_level}")
    print_stage("服务启动")
    print_loading("FastAPI 服务启动中...")

    # 设置全局服务器配置
    global server_host, server_port
    server_host = args.host
    server_port = args.port

    # 使用全局应用实例
    global app

    print_success("FastAPI 服务已启动")

    print_stage("服务信息")
    print_info(f"🏠 http://{args.host}:{args.port}/")
    print_info(f"🔌 ws://{args.host}:{args.port}/ws")
    print_info(f"📚 http://{args.host}:{args.port}/docs")
    print_info(f"💚 http://{args.host}:{args.port}/health")

    # 启动服务器
    uvicorn.run(
        app,
        host=args.host,
        port=args.port,
        reload=args.reload,
        log_level=args.log_level,
        access_log=False,  # 禁用访问日志
        server_header=False,  # 禁用服务器头信息
        date_header=False,  # 禁用日期头信息
    )


def setup_global_logging(level: str = "INFO"):
    logging.basicConfig(
        level=level.upper(),
        format="%(asctime)s | %(levelname)-8s | %(name)s:%(funcName)s:%(lineno)d - %(message)s",
        datefmt="%Y-%m-%d %H:%M:%S"
    )
    for noisy_module in ["jieba", "modelscope", "funasr"]:
        logging.getLogger(noisy_module).setLevel(logging.WARNING)


def main() -> None:
    """主函数 - 统一入口点"""
    parser = create_parser()
    global args
    args = parser.parse_args()

    # 设置日志级别，并屏蔽第三方库 DEBUG 日志
    setup_global_logging(args.log_level)

    # 启动服务器（包含 WebSocket 服务）
    start_server(args)


# 全局变量存储服务器配置
server_host = "127.0.0.1"
server_port = 8000

# 创建全局应用实例，供 uvicorn 直接导入使用
app = create_fastapi_app()

if __name__ == "__main__":
    main()
